package com.hengpeng.itfinoss.service.impl;

import java.util.Date;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map.Entry;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import com.hengpeng.common.exception.ServiceResult;
import com.hengpeng.common.persist.entity.AbstractEntity.BoolValue;
import com.hengpeng.common.persist.query.DynamicQuery;
import com.hengpeng.common.persist.query.model.Order.OrderType;
import com.hengpeng.common.scheduling.entity.SystemJob;
import com.hengpeng.common.scheduling.entity.SystemJob.SystemJobState;
import com.hengpeng.common.util.NetworkUtil;
import com.hengpeng.itfinoss.service.ServiceFactory;
import com.hengpeng.itfinoss.service.SystemJobService;

/**
 * <pre>
 * 系统作业服务实现
 * </pre>
 * @author pengfangliang
 * @version 1.0, 2010-9-19
 */
@Transactional
@Service("OSSSystemJobServiceImpl")
@Lazy
public class SystemJobServiceImpl implements SystemJobService
{

	@Autowired
	private ServiceFactory serviceFactory;

	@Transactional(propagation = Propagation.REQUIRES_NEW)
	public SystemJob checkJob(String className, String taskName, String taskDescription)
	{
		SystemJob systemJob = serviceFactory.getSystemJobService().getSystemJobByClassName(className);
		if (systemJob.getClassName()==null||systemJob.getClassName().equals(""))
		{
			systemJob = new SystemJob();
			systemJob.setCanRun(BoolValue.YES);
			systemJob.setClassName(className);
			systemJob.setDescription(taskDescription);
			systemJob.setLastCompleteTime(new Date());
			systemJob.setLastRunHostName(NetworkUtil.getHostName());
			systemJob.setLastStartTime(new Date());
			systemJob.setRunCount(0);
			systemJob.setRunState(SystemJobState.WAITING);
			systemJob.setSuccessCount(0);
			systemJob.setFailureCount(0);
			systemJob.setTaskName(taskName);
			systemJob.setTimeoutCount(0);
			systemJob = serviceFactory.getPersistService().save(systemJob);
		}
		return systemJob;
	}

	@Transactional(propagation = Propagation.REQUIRES_NEW)
	public void execOverSystemJob(String className, boolean isSuccess, int runCount)
	{
		SystemJob __systemJob = serviceFactory.getSystemJobService().getSystemJobByClassName(className);
		__systemJob.setLastRunHostName(NetworkUtil.getHostName());
		if (__systemJob.getRunCount().equals(runCount))
		{
			__systemJob.setRunState(SystemJobState.WAITING);
			__systemJob.setLastCompleteTime(new Date());
		}
		if (isSuccess)
		{
			__systemJob.setSuccessCount(__systemJob.getSuccessCount() + 1);
		}
		else
		{
			__systemJob.setFailureCount(__systemJob.getFailureCount() + 1);
		}
		serviceFactory.getSystemJobService().update(__systemJob);
	}

	@Transactional(propagation = Propagation.REQUIRES_NEW)
	public ServiceResult<SystemJob> execSystemJob(String className, int timeout)
	{
		SystemJob _systemJob = serviceFactory.getPersistService().get(SystemJob.class, className);
		boolean isExec = false;// 是否可以执行
		boolean isTimeout = false;// 定时任务是否超时

		if (_systemJob.getRunState() == SystemJobState.WAITING)
		{
			isExec = true;
		}
		else if (_systemJob.getRunState() == SystemJobState.RUNING && timeout != -1)
		{
			long runtimeNum = new Date().getTime() - _systemJob.getLastStartTime().getTime();
			if (runtimeNum > timeout)
			{
				isTimeout = true;
			}
		}
		if (isExec || isTimeout)
		{
			_systemJob.setLastStartTime(new Date());
			_systemJob.setRunCount(_systemJob.getRunCount() + 1);
			if (isTimeout)
			{
				_systemJob.setTimeoutCount(_systemJob.getTimeoutCount() + 1);
			}
			_systemJob.setRunState(SystemJobState.RUNING);
			serviceFactory.getSystemJobService().update(_systemJob);
			return new ServiceResult<SystemJob>(_systemJob);
		}
		return new ServiceResult<SystemJob>();
	}

	@Override
	public ServiceResult<Long> selectSystemJobCount(String taskName, String desc, BoolValue canRun,
			String lastRunHostName, SystemJobState runState)
	{
		DynamicQuery pagination = new DynamicQuery(SystemJob.class);
		if (taskName != null && taskName.trim().length() > 0)
			pagination.like("taskName", "%" + taskName + "%");
		if (desc != null && desc.trim().length() > 0)
			pagination.like("description", "%" + desc + "%");
		if (canRun != null && canRun.getText().trim().length() > 0)
			pagination.eq("canRun", canRun);
		if (lastRunHostName != null && lastRunHostName.trim().length() > 0)
			pagination.like("lastRunHostName", "%" + lastRunHostName + "%");
		if (runState != null && runState.getText().trim().length() > 0)
			pagination.eq("runState", runState);
		return new ServiceResult<Long>(serviceFactory.getPersistService().findPageCount(pagination, null));
	}

	@Override
	public ServiceResult<List<SystemJob>> selectSystemJobPage(String taskName, String desc, BoolValue canRun,
			String lastRunHostName, SystemJobState runState, Integer pageIndex, Integer pageSize,
			LinkedHashMap<String, OrderType> sortMap)
	{
		DynamicQuery pagination = new DynamicQuery(SystemJob.class);
		if (taskName != null && taskName.trim().length() > 0)
			pagination.like("taskName", "%" + taskName + "%");
		if (desc != null && desc.trim().length() > 0)
			pagination.like("description", "%" + desc + "%");
		if (canRun != null && canRun.getText().trim().length() > 0)
			pagination.eq("canRun", canRun);
		if (lastRunHostName != null && lastRunHostName.trim().length() > 0)
			pagination.like("lastRunHostName", "%" + lastRunHostName + "%");
		if (runState != null && runState.getText().trim().length() > 0)
			pagination.eq("runState", runState);
		pagination.setPageIndex(pageIndex);
		pagination.setPageSize(pageSize);
		if (sortMap != null)
		{
			for (Entry<String, OrderType> entry : sortMap.entrySet())
			{
				if (entry.getValue() == OrderType.DESC)
				{
					pagination.desc(entry.getKey());
				}
				else
				{
					pagination.asc(entry.getKey());
				}
			}
		}
		return new ServiceResult<List<SystemJob>>(serviceFactory.getPersistService().find(SystemJob.class, pagination));
	}

	@Override
	public ServiceResult<SystemJob> update(SystemJob sysJob)
	{
		SystemJob systemJob = serviceFactory.getPersistService().update(sysJob);
		return new ServiceResult<SystemJob>(systemJob);
	}

	@Override
	public SystemJob getSystemJobByClassName(String className)
	{
		SystemJob sysjob = new SystemJob();
		DynamicQuery query = new DynamicQuery(SystemJob.class);
		query.eq("className", className);
		List<SystemJob> sysjobList = serviceFactory.getPersistService().find(SystemJob.class, query);
		if (null != sysjobList && !sysjobList.isEmpty())
		{
			sysjob = sysjobList.get(0);
		}
		return sysjob;
	}

	@Override
	public int resetitfinossSystemJob()
	{
		
		return 0;
	}
}
